;
(function (doc) {
  //----节点----
  // 导航栏ul
  var oNav = doc.getElementsByClassName('J_nav')[0],
    //导航栏所有子项 li
    oNavItems = oNav.getElementsByClassName('nav-item'),
    //导航栏所有子项的长度
    oNavItemsLen = oNavItems.length,
    //课程搜索下的搜索 盒子 
    oSearchRow = doc.getElementsByClassName('J_searchRow')[0],
    //表格标题内部的 提示内容
    oWarningTip = doc.getElementsByClassName('J_tipRow')[0],
    //表格tbody内部区域列表信息
    oCourseList = doc.getElementsByClassName('J_courseList')[0],
    //搜索输入框
    oSearchInput = doc.getElementById('J_searchInput'),
    //页码按钮 盒子
    oPageBtnRow = doc.getElementsByClassName('J_pageBtnRow')[0],
    //页码列表 ul
    oPageBtnList = doc.getElementsByClassName('J_pageBtnList')[0],
    //所有页码的li 
    oBtnItems = oPageBtnList.getElementsByClassName('btn-item'),
    //所有课程名称input文本框 
    oCourseInputs = oCourseList.getElementsByClassName('course-name-input'),
    //所有课程名称span标签
    oCourseSpans = oCourseList.getElementsByClassName('course-name'),
    //----模板----
    //列表模板
    listItemTpl = doc.getElementById('J_listItemTpl').innerHTML,
    //分页模板
    pageBtnItemTpl = doc.getElementById('J_pageBtnItemTpl').innerHTML,
    //将导航栏所有子项 li里的data-field的值初始为manage
    field = 'manage',
    //初始化页码
    pageNum = 0,
    //初始化课程名称项的id
    curId = 0,
    //初始化课程名称项的下标
    curIdx = -1;

  var API = {
    getCourseList: 'http://localhost/api_for_study/index.php/List/getCourseListForManage',
    getSearchList: 'http://localhost/api_for_study/index.php/List/getSearchListForManage',
    doListItem: 'http://localhost/api_for_study/index.php/List/doListItemForManage',
    updateCourseName: 'http://localhost/api_for_study/index.php/List/updateCourseNameForManage'
  }

  var init = function () {
    //首次加载页面加载 列表管理数据
    getCourseList(field, pageNum);
    bindEvent();
  }

  function bindEvent() {
    //事件代理：点击导航栏子选项触发事件 列表管理/垃圾箱/课程搜索
    oNav.addEventListener('click', navClick, false);
    //输入框绑定事件 
    //节流 throttle(fn, delay)
    oSearchInput.addEventListener('input', throttle(courseSearch, 1000), false);
    //事件代理：点击页码数字触发事件 1/2/3 ...
    oPageBtnList.addEventListener('click', changePage, false);
    //事件代理：通过绑定列表内容页 点击 删除/恢复 操作按钮
    oCourseList.addEventListener('click', listClick, false);
  }

  //事件处理函数：点击导航栏子选项触发事件 列表管理/垃圾箱/课程搜索
  function navClick(e) {
    var e = e || window.event,
      tar = e.target || e.srcElement,
      className = tar.className,
      oParent,
      item;

    //阻止往上冒泡
    e.stopPropagation();

    // a标签
    if (className === 'nav-lk') {
      oParent = tar.parentNode,
        oNavItemsLen = oNavItems.length;

      for (var i = 0; i < oNavItemsLen; i++) {
        item = oNavItems[i];
        item.className = 'nav-item';
      }
      oParent.className += ' active';
    }

    //点击li获取当前data-field里的值 manage/trash/search
    field = oParent.getAttribute('data-field')

    if (field === 'search') {
      //显示暂无数据
      showWarningTip(true);
      //显示课程搜索里面的 搜索框
      showSearchInput(true);
      //隐藏页码按钮 样式
      showPageBtnRow(false);
      return;
    }
    //回归为首页
    pageNum = 0;
    //隐藏课程搜索里面的 搜索框
    showSearchInput(false);
    //请求课程列表
    getCourseList(field, pageNum);
  }

  //事件处理函数：输入文本内容搜索指定内容显示在列表
  function courseSearch(e) {
    var e = e || window.event,
      val = trimSpace(this.value),
      valLen = val.length;

    //阻止往上冒泡
    e.stopPropagation();

    if (valLen > 0) {
      getSearchList(val);
    } else {
      //没有数据，显示暂无数据
      showWarningTip(true);
    }
  }

  //事件处理函数：点击页码数字触发事件 1/2/3 ...
  function changePage(e) {
    var e = e || window.event,
      tar = e.target || e.srcElement,
      className = tar.className,
      oParent = tar.parentNode,
      oBtnItemsLen,
      item,
      //找到当前项的下标
      thisIdx = [].indexOf.call(oBtnItems, oParent);

    //阻止往上冒泡
    e.stopPropagation();

    // a标签
    if (className === 'page-btn') {
      oBtnItemsLen = oBtnItems.length;

      for (var i = 0; i < oBtnItemsLen; i++) {
        item = oBtnItems[i];
        item.className = 'btn-item';
      }
      oParent.className += ' cur';
      // getCourseList(field, 需要每次切换出来的页码对应下标);
      getCourseList(field, thisIdx);
    }
  }

  //事件处理函数：点击 删除/恢复 操作按钮
  function listClick(e) {
    var e = e || window.event,
      tar = e.target || e.srcElement,
      className = tar.className,
      itemId = tar.getAttribute('data-id');

    //阻止往上冒泡
    e.stopPropagation();

    switch (className) {
      case 'list-btn delete':
        var c = confirm('确认删除');
        //c为真才往下执行
        c && doListItem('delete', pageNum, itemId);
        break;
      case 'list-btn regain':
        var c = confirm('确认恢复');
        //c为真才往下执行
        c && doListItem('regain', pageNum, itemId);
        break;
      case 'course-name':
        //先隐藏所有再显示被点中的
        hideAllInput();
        showInput(tar);
        break;
      default:
        break;
    }
  }

  //事件处理函数：更新课程名称
  function updateCourseName(e) {
    var e = e || window.event,
      eventType = e.type;

    //判断鼠标click/键盘keyup
    if (eventType === 'keyup') {
      var keyCode = e.keyCode;
      //回车键
      if (keyCode === 13) {
        submitNewCourseName(curId, curIdx);
      }
      return;
    }
    //click的情况：
    submitNewCourseName(curId, curIdx);
  }

  //请求获取列表
  function getCourseList(field, pageNum) {
    xhr.ajax({
      url: API.getCourseList,
      type: 'POST',
      dataType: 'JSON',
      data: {
        field: field,
        pageNum: pageNum
      },
      success: function (data) {
        _setData(field, data, pageNum);
      },
      error: function () {
        alert('列表获取失败，请重试!');
      }
    })
  }

  // 搜索指定内容显示在列表
  function getSearchList(keyword) {
    xhr.ajax({
      url: API.getSearchList,
      type: 'POST',
      dataType: 'JSON',
      data: {
        keyword: keyword
      },
      success: function (data) {
        _setData('manage', data);
      },
      error: function () {
        alert('搜索列表失败，请重试!');
      }
    })
  }

  /**
   * 修改当前列表数据 恢复/删除 操作
   * @param {*} type 恢复/删除
   * @param {*} pageNum 当前页
   * @param {*} itemId 恢复/删除的当前项的id
   */
  function doListItem(type, pageNum, itemId) {
    xhr.ajax({
      url: API.doListItem,
      type: 'POST',
      dataType: 'JSON',
      data: {
        type: type,
        pageNum: pageNum,
        itemId: itemId
      },
      success: function (data) {
        _setData(field, data, pageNum);
      },
      error: function () {
        alert('操作列表失败，请重试!');
      }
    });
  }

  /**
   * 提交新的课程名称
   * @param {*} curId 当前项id 便于后端找到修改的id
   * @param {*} curIdx 当前项下标，便于修改input
   */
  function submitNewCourseName(curId, curIdx) {
    //关闭所有输入框且失去所有的输入框焦点
    hideAllInput();
    //获取新的课程名称
    var newVal = oCourseInputs[curIdx].value,
      //当前选中的span
      thisCourseSpan = oCourseSpans[curIdx];

    //如果新的输入框内容跟当前选中的文本输入框的内容不相同时，发送修改数据请求
    if (newVal !== thisCourseSpan.innerHTML) {
      //请求修改数据的接口
      xhr.ajax({
        url: API.updateCourseName,
        type: 'POST',
        dataType: 'JSON',
        data: {
          itemId: curId,
          newVal: newVal
        },
        success: function (data) {
          if (data === 'success') {
            thisCourseSpan.innerHTML = newVal;
          } else {
            alert('修改课程名称失败，请重试!');
          }
          //重置curId/curIdx
          curId = 0;
          curIdx = -1;
        },
        error: function () {
          alert('修改课程名称失败，请重试!');
        }
      });
    }
  }

  /**
   * 渲染课程列表模板
   * @param {*} listField manage/trash/search的列表
   * @param {*} data 
   */
  function renderList(listField, data) {
    var list = '';
    data.forEach(function (elem) {
      list += listItemTpl.replace(/{{(.*?)}}/g, function (node, key) {
        return {
          id: elem.id,
          course: elem.course,
          hour: elem.hour,
          teacher: elem.teacher,
          field: elem.field,
          //regain类名：恢复 / delete类名：删除
          type: listField == 'trash' ? 'regain' : 'delete',
          typeText: listField == 'trash' ? '恢复' : '删除'
        } [key];
      })
    })
    return list;
  }

  /**
   * 渲染底部页码按钮
   * @param {*} pageCount 总页数
   * @param {*} pageNum 当前页
   */
  function renderPageBtns(pageCount, pageNum) {
    var list = '';
    for (var i = 0; i < pageCount; i++) {
      list += pageBtnItemTpl.replace(/{{(.*?)}}/g, function (node, key) {
        return {
          pageNum: i + 1,
          //如果i的数值等于当前页的数值, 将为isCur新增类名cur
          isCur: i == pageNum && 'cur'
        } [key];
      });
    }
    return list;
  }

  /**
   * 处理Ajax里success函数响应回来的data数据
   * @param {*} field data-field的值 manage/trash/search
   * @param {*} data 服务器响应回来的数据
   * @param {*} pageNum 当前页
   * 
   */
  function _setData(field, data, pageNum) {
    //响应的数据和页码
    var res = data.res,
      pageCount = data.pages;

    //res存在且大于0证明为有效数据
    if (res && res.length > 0) {
      oCourseList.innerHTML = renderList(field, res);
      showWarningTip(false);

      // 只有数据大于一页的时候且search是因为通过输入数据搜索内容所以没有分页的
      if (pageCount && field !== 'search') {
        //渲染底部页码按钮
        //将替换好的字符串模板赋值给ul的文本
        oPageBtnList.innerHTML = renderPageBtns(pageCount, pageNum);
        //显示页码按钮 样式
        showPageBtnRow(true);
      } else {
        //清空底部页码按钮 ul
        oPageBtnList.innerHTML = '';
        //隐藏页码按钮 样式
        showPageBtnRow(false);
      }
    } else {
      showWarningTip(true);
    }
  }

  //是否显示 暂无数据
  function showWarningTip(show) {
    if (show) {
      //显示 暂无数据
      oWarningTip.className = 'J_tipRow tip-row';
      //清空表格tbody内部区域列表信息
      oCourseList.innerHTML = '';
    } else {
      //隐藏 暂无数据
      oWarningTip.className += ' hide';
    }
  }

  //是否显示 课程搜索里面的 搜索框
  function showSearchInput(show) {
    if (show) {
      oSearchRow.className += ' show';
    } else {
      oSearchRow.className = 'J_searchRow search-row'
    }
  }

  //是否显示 底部分页按钮
  function showPageBtnRow(show) {
    if (show) {
      oPageBtnRow.className += ' show';
    } else {
      oPageBtnRow.className = 'page-btn-row J_pageBtnRow';
    }
  }

  /**
   * 功能一：显示 当前项课程名称里的 输入文本框
   * 功能二：绑定document事件
   * @param {*} target 被传入的span标签
   */
  //显示 当前项课程名称里的 输入文本框
  function showInput(target) {
    // span标签的父节点是td标签，类名是course-name-cell
    var oParent = target.parentNode,
      //找到td标签下的子节点input标签，类名是course-name-input
      thisInput = oParent.getElementsByClassName('course-name-input')[0],
      //输入框文本的值的长度
      thisInputLen = thisInput.value.length;

    //缓存下curId到全局
    curId = thisInput.getAttribute('data-id');
    //缓存下curIdx到全局
    // curIdx = [].indexOf.call(Allspans, span);
    //或者 curIdx = [].indexOf.call(AllInputs, input);
    curIdx = [].indexOf.call(oCourseSpans, target);

    //新增show类名
    thisInput.className += ' show';
    //让当前input 聚焦
    thisInput.focus();
    //让输入框内容为全选中状态
    //setSelectionRange(从哪开始选,选到哪里)
    thisInput.setSelectionRange(0, thisInputLen);

    //事件代理：失去文本输入框焦点 触发提交数据请求
    document.addEventListener('click', updateCourseName, false);
    //事件代理：失去文本输入框焦点 触发提交数据请求
    document.addEventListener('keyup', updateCourseName, false);
  }

  /**
   * 隐藏除了当前选中课程名称的其余课程 关闭输入文本框
   * 功能一：关闭所有输入文本框
   * 功能二：且让所有的文本框失去焦点
   * 功能三：解除document的事件绑定
   */
  function hideAllInput() {
    var inputsLen = oCourseInputs.length,
      item;

    for (var i = 0; i < inputsLen; i++) {
      item = oCourseInputs[i];
      item.className = 'course-name-input';
      //让所有input失去焦点
      item.blur();

      //事件代理：失去文本输入框焦点 触发提交数据请求
      document.removeEventListener('click', updateCourseName, false);
      //事件代理：失去文本输入框焦点 触发提交数据请求
      document.removeEventListener('keyup', updateCourseName, false);
    }
  }

  init();

})(document);